﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using Kiiro.Common.Entities;

namespace Kiiro.Model.Utility
{
    public class DelegateComparer<T> : IEqualityComparer<T>
    {
        private Func<T, T, bool> _equals;
        private Func<T, int> _getHashCode;

        public DelegateComparer ( Func<T, T, bool> equals )
        {
            this._equals = equals;
        }

        public DelegateComparer ( Func<T, T, bool> equals, Func<T, int> getHashCode )
        {
            this._equals = equals;
            this._getHashCode = getHashCode;
        }

        public bool Equals ( T a, T b )
        {
            return _equals ( a, b );
        }

        public int GetHashCode ( T a )
        {
            if ( _getHashCode != null )
                return _getHashCode ( a );
            else
                return a.GetHashCode ( );
        }
    }

    /// <summary>
    /// Overloaded Comparer that takes a User Collection and checks if the Logins match ONLY,
    ///     if you need the whole object use the DelegateComparer
    /// </summary>
    public class DelegateUserLoginComparer<T> : IEqualityComparer<T>
    {
        private Func<T, T, bool> _equals;
        private Func<string, int> _getHashCode;

        public DelegateUserLoginComparer ( Func<T, T, bool> equals )
        {
            this._equals = equals;
        }

        public DelegateUserLoginComparer ( Func<T, T, bool> equals, Func<string, int> getHashCode )
        {
            this._equals = equals;
            this._getHashCode = getHashCode;
        }

        public bool Equals ( T a, T b )
        {
            if ( !( a is User ) && !( b is User ) )
                return false;
            return String.Compare ( ( a as User ).Login, ( b as User ).Login, StringComparison.OrdinalIgnoreCase ) == 0;
        }

        public int GetHashCode ( T u )
        {
            if ( u is User )
            {
                if ( _getHashCode != null )
                    return _getHashCode ( ( u as User ).Login );
                else
                    return ( u as User ).Login.GetHashCode ( );
            }
            else return u.GetHashCode ( );
        }
    }
}